<?php
/**
 * OfferController is used for management of offers.
 * 
 * LBB Solutions Oy 版权所有 © 2013
 */
class OfferController extends Controller
{
	/**
	 * @return array action filters
	 */
	public function filters() {
		return array(
			'accessControl', // perform access control for CRUD operations
			array(
                'COutputCache + stats, reportDaily', // Cache for pages
                'duration' => 8 * 3600,    // 1/3 day caching
				'varyByParam' => array('id'),
				'varyByExpression' => 'Yii::app()->language',
				'varyBySession' => true,
            ),
		);
	}
	
	/**
	 * Specifies the access control rules.
	 * This method is used by the 'accessControl' filter.
	 * @return array access control rules
	 */
	public function accessRules() {
		return array(
			array('allow', // allow authenticated user to perform below actions
				'users'=>array('@'),
			),
			array('deny',  // deny all users
				'users'=>array('*'),
			),
		);
	}

	/**
	 * List of offers
	 */
	public function actionIndex() {
		//handle page=?
		$page_size = Yii::app()->params['pageSize'];
		$current_page = Yii::app()->request->getParam('page', 1);
		$offset = ($current_page - 1) * $page_size;
		$sql_limit = " LIMIT {$offset}, {$page_size} ";
		
		$params = array('id_merchant'=>(int)Yii::app()->user->id);
		$sql_where = '';
		
		//post filter_week=?
		$filter_week = Yii::app()->request->getPost('filter_week', 0);
		if ($filter_week > 0 and $filter_week < 8) {
			$sql_where .= ' AND s.week_days LIKE :week_days';
			$params['week_days'] = "%{$filter_week}%";
		}
		//post filter_status
		$filter_status = Yii::app()->request->getPost('filter_status', '');
		if ($filter_status === '1') {
			$sql_where .= ' AND s.status=1';
		} else if ($filter_status === '0') {
			$sql_where .= ' AND (s.status is null OR s.status=0)';
		}
		//post filter_date
		$filter_date = Yii::app()->request->getPost('filter_date', '');
		if ($filter_date === '0') {
			//current
			$sql_where .= ' AND s.start_date<NOW() AND s.end_date>NOW()';
		} else if ($filter_date === '1') {
			//upcoming
			$sql_where .= ' AND s.start_date>NOW()';
		} else if ($filter_date === '2') {
			//expired
			$sql_where .= ' AND s.end_date<NOW()';
		} else if ($filter_date === '3') {
			//current + upcoming
			$sql_where .= ' AND s.end_date>NOW()';
		}
		
		$sql_orderby = ' ORDER BY completed ASC, s.update_timestamp DESC, s.insert_timestamp DESC ';
		$sql_offer = 'SELECT s.id, s.url_picture, m.url_logo, m.url_offer_img, s.content,
			s.show_price, s.price, s.value, s.discount,
			s.show_hours, s.start_hour, s.end_hour, s.week_days, s.status, s.type,
			(NOW() > s.end_date) AS completed, UNIX_TIMESTAMP(s.published_time) AS uts_published_time,
			UNIX_TIMESTAMP(s.start_date) AS uts_start_date, UNIX_TIMESTAMP(s.end_date) AS uts_end_date,
			SUM(d.reach) as reach, SUM(d.clicks) as clicks, SUM(d.notifications) as notifications, SUM(d.spread) as spread, SUM(d.redeems) as redeems
			FROM tbl_merchant_special s
			INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			LEFT JOIN tbl_merchant_special_report_day d ON d.id_special=s.id
			WHERE s.id_merchant=:id_merchant AND s.trash=0 ' . $sql_where
			. ' GROUP BY s.id '
			. $sql_orderby
			. $sql_limit;
		$sql_count = 'SELECT COUNT(s.id) AS total FROM tbl_merchant_special s INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id_merchant=:id_merchant AND s.trash=0 ' . $sql_where;
		
		//count current/upcoming/expired specials
		$sql_special_num = 'SELECT 
			(SELECT COUNT(s.id) AS total FROM tbl_merchant_special s INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id_merchant=:id_merchant AND s.trash=0 AND s.start_date<NOW() AND s.end_date>NOW()) as current,
			(SELECT COUNT(s.id) AS total FROM tbl_merchant_special s INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id_merchant=:id_merchant AND s.trash=0 AND s.start_date>NOW()) as upcoming,
			(SELECT COUNT(s.id) AS total FROM tbl_merchant_special s INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id_merchant=:id_merchant AND s.trash=0 AND s.end_date<NOW()) as expired ';
		
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_offer);
		$rows = $command->queryAll(true, $params);
		$command = $connection->createCommand($sql_count);
		$aTotal = $command->queryRow(true, $params);
		$command = $connection->createCommand($sql_special_num);
		$aNumber = $command->queryRow(true, $params);
		$connection->active = false;
		
		//set pager
		$pages = new CPagination($aTotal['total']);
		$pages->setPageSize($page_size);
		if (Yii::app()->request->isAjaxRequest) {
			$this->renderPartial('_list', array('model' => $rows, 'pages' => $pages));
		} else {
			$this->render('index', array('model' => $rows, 'pages' => $pages, 'number' => $aNumber));
		}
	}
	
	/**
	 * The performance bars for this month and last month.
	 */
	public function actionStats() {
		if (!Yii::app()->request->isAjaxRequest) {
			throw new CHttpException(404, 'The requested page is only for AJAX request.');
		}
		
		$sql_monthly = 'SELECT MONTH(local_date) as month, YEAR(local_date) as year, COUNT(DISTINCT id_special) AS offers,
			SUM(d.reach) as reach, SUM(d.clicks) as clicks, SUM(d.notifications) as notifications, SUM(d.spread) as spread, SUM(d.redeems) as redeems
			FROM tbl_merchant_special_report_day d
			INNER JOIN tbl_merchant_special s ON s.id=d.id_special
			INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id_merchant=:id_merchant AND UNIX_TIMESTAMP(local_date)>=:last_2_month_ts
			GROUP BY month
			ORDER BY month ASC ';
		$params = array(
			':id_merchant' => Yii::app()->user->id,
			':last_2_month_ts' => mktime(0,0,0, date('n')-1, 1, date('Y')),
		);
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_monthly);
		$rows = $command->queryAll(true, $params);
		$connection->active = false;
		
		$this->renderPartial('_chart_stats', array(
			'rows' => $rows,
		));
	}
	
	/**
	 * The latest 6 active offers
	 */
	public function actionRecent() {
		if (!Yii::app()->request->isAjaxRequest) {
			throw new CHttpException(404, 'The requested page is only for AJAX request.');
		}
		
		$sql_offers = 'SELECT s.id, s.url_picture, m.url_logo, m.url_offer_img, s.content,
			s.price, s.value, s.discount, s.show_hours, s.start_hour, s.end_hour, s.week_days, s.status, s.type,
			(NOW() > s.end_date) AS completed, UNIX_TIMESTAMP(s.published_time) AS uts_published_time,
			UNIX_TIMESTAMP(s.start_date) AS uts_start_date, UNIX_TIMESTAMP(s.end_date) AS uts_end_date,
			SUM(d.reach) as reach, SUM(d.clicks) as clicks, SUM(d.notifications) as notifications, SUM(d.spread) as spread, SUM(d.redeems) as redeems
			FROM tbl_merchant_special s
			INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			LEFT JOIN tbl_merchant_special_report_day d ON d.id_special=s.id
			WHERE s.id_merchant=:id_merchant AND s.trash=0 AND s.status=1 AND s.end_date>NOW()
			GROUP BY s.id
			ORDER BY s.published_time DESC
			LIMIT 5';
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_offers);
		$rows = $command->queryAll(true, array(
			':id_merchant'=>Yii::app()->user->id,
		));
		$connection->active = false;
		$this->renderPartial('_recent', array(
			'rows' => $rows,
		));
	}
	
	/**
	 * Create or edit an offer with form page.
	 */
	public function actionForm($id = null) {
		$model = empty($id) ? new SpecialForm() : $this->_loadModel((int)$id);
		//throw exception if status=1(published)
		if ($model->status > 0) {
			throw new CHttpException(404, 'You cannot edit a published special!');
		}
		
		// if it is ajax validation request
		if (isset($_POST['ajax']) && $_POST['ajax'] === 'special-form') {
			echo CActiveForm::validate($model);
			Yii::app()->end();
		}
		
		// collect user input data
		if (isset($_POST['SpecialForm'])) {
			$model->attributes = $_POST['SpecialForm'];
			$model->id_merchant = Yii::app()->user->id;
			
			$model->content = strip_tags($_POST['SpecialForm']['content']);
			$model->start_hour = $_POST['SpecialForm']['start_hour'];
			$model->end_hour = $_POST['SpecialForm']['end_hour'];
			if (isset($_POST['SpecialForm']['show_hours']) and $_POST['SpecialForm']['show_hours'] == 0) {
				$model->show_hours = 0;
			} elseif (!empty($model->start_hour) and !empty($model->end_hour)) {
				$model->show_hours = 1;
			}
			
			//offer date range
			$model->start_date = date('Y-m-d',strtotime($_POST['SpecialForm']['start_date']));
			if (empty($_POST['SpecialForm']['end_date'])) $model->end_date = $model->start_date;
			else $model->end_date = date('Y-m-d',strtotime($_POST['SpecialForm']['end_date']));
			//offer time range
			if (empty($model->end_hour)) {
				$model->end_date .= ' 23:59:59';
			} else {
				$postfix_time = BUtils::GetEndHourFormat($model->end_hour);
				$model->end_date .= ' ' . $postfix_time;
			}

			//set week_days
			$model->week_days = (isset($_POST['SpecialForm']['week_days'])) ? implode(',', $_POST['SpecialForm']['week_days']) : date('N');
			
			//set the url_picture
			$model->url_picture = $_POST['SpecialForm']['url_picture'];
			
			//set offer price and discount
			if (!empty($_POST['SpecialForm']['price'])) {
				$model->price = $_POST['SpecialForm']['price'];
			} else {
				$model->price = new CDbExpression('NULL');
			}
			if (!empty($_POST['SpecialForm']['value'])) {
				$model->value = $_POST['SpecialForm']['value'];
			} else {
				$model->value = new CDbExpression('NULL');
			}
			if (!empty($_POST['SpecialForm']['discount'])) {
				$model->discount = $_POST['SpecialForm']['discount'];
			} else {
				$model->discount = new CDbExpression('NULL');
			}
			
			$model->type = 1;
			$model->update_timestamp = new CDbExpression('NOW()');
			
			//get the browser info: client_type, agent_string
			$model->client_type = 'Web';
			$model->agent_string = Yii::app()->request->getUserAgent();
			
			if ($model->save()) {
				$url = $this->createUrl('index', array('id'=>$model->id));
				Yii::app()->request->redirect($url);
			} else {
				Yii::app()->user->setFlash('saved', 'System error was happen when you saved!');
				$this->refresh();
			}
		} else {
			//get merchant's profile
			$sql_merchant = ' SELECT m.id, m.name, m.address, m.postcode, m.phone, m.city, m.country_code, m.currency_code,
			m.url_logo, m.url_site, m.url_offer_img, h.open_hour, h.close_hour
			FROM tbl_merchant_account m
			LEFT JOIN tbl_merchant_open_hours h ON h.id_merchant=m.id AND h.week_no=:week_no
			WHERE m.id=:id ';
			$connection = Yii::app()->db;
			$command = $connection->createCommand($sql_merchant);
			$row = $command->queryRow(true, array(':id'=>Yii::app()->user->id, ':week_no'=>date('N')));
						
			//add sid=100980 to use the old offer's info
			$sid = Yii::app()->request->getQuery('sid');
			if (!empty($sid) and empty($id)) {
				$model_old = $this->_loadModel((int)$sid);
				$model->content = $model_old->content;
				$model->url_picture = $model_old->url_picture;
				$model->price = $model_old->price;
				$model->value = $model_old->value;
				$model->discount = $model_old->discount;
				$model->max_number = $model_old->max_number;
				$model->type = $model_old->type;
				//keep the hours range
				$model->start_hour = $model_old->start_hour;
				$model->end_hour = $model_old->end_hour;
				$model->week_days = $model_old->week_days;
			}
			
			//get the template content
			$templateId = Yii::app()->request->getQuery('tid');
			if (!empty($templateId)) {
				$sql_template = 'SELECT t.url_picture, t.content, t.price, t.value, t.discount
					FROM tbl_merchant_special_template t
					WHERE t.id_merchant=:id_merchant AND t.id=:id ';
				$command = $connection->createCommand($sql_template);
				$tempRow = $command->queryRow(true, array(':id_merchant'=>Yii::app()->user->id, ':id'=>$templateId));
				$model->content = $tempRow['content'];
				$model->url_picture = $tempRow['url_picture'];
				$model->price = $tempRow['price'];
				$model->value = $tempRow['value'];
				$model->discount = $tempRow['discount'];
			}
			$connection->active = false;
			
			//set the current business hours as default value
			if (empty($model->start_hour)) $model->start_hour = $row['open_hour'];
			if (empty($model->end_hour)) $model->end_hour = $row['close_hour'];
			
			$model->type = 1;//must set to 1
			$row['thumbs'] = array();
			$this->render('form', array('model' => $model, 'r'=>$row));
		}
	}
	
	/**
	 * Insert url_offer_img picture with AJAX.
	 * 96x96 + 640x320
	 */
	public function actionUploadOfferImage()
	{
		$specialId = Yii::app()->request->getQuery('id');
		if (empty($specialId)) {
			$specialId = time();
		}
		$specialId .= rand(100, 999);
		
		//set folder
		$saved_folder = BUtils::GetUploadingFolder(Yii::app()->user->id);
		$url_folder = BUtils::GetUploadingUrl(Yii::app()->user->id);
		
		Yii::import("ext.EAjaxUpload.qqFileUploader");
		$allowedExtensions = array("jpg","jpeg","gif","png");
		$sizeLimit = 8 * 1024 * 1024;
		$uploader = new qqFileUploader($allowedExtensions, $sizeLimit);
		$result = $uploader->handleUpload($saved_folder, 'offer_' . $specialId, true);
		unset($uploader);
		
		//set thumb
		$thumb = 'thumb_' . $result['filename'];
		//resize offer picture to 640 x 360 size:
		Yii::import('ext.iwi.Iwi');
		$picture = new Iwi($saved_folder . $result['filename']);
		// resize to 640x360: 16:9
		$picture->adaptive(640, 360);
		$picture->save($saved_folder . $result['filename']);
		// resize to 108x108
		$picture->adaptive(192, 108);
		$picture->crop(108, 108);
		$picture->save($saved_folder . $thumb);
		unset($picture);
		
		$result['url_offer_img'] = $url_folder . $result['filename'] . '?t=' . time();
		$result['url_offer_img_db'] = $url_folder . $thumb;
		echo htmlspecialchars(json_encode($result), ENT_NOQUOTES);
	}
	
	/**
	 * AJAX publish a special.
	 */
	public function actionPublish($id) {
		//update status=1, published_time=NOW() (only for status=0)
		$connection = Yii::app()->db;
		$command = $connection->createCommand('UPDATE tbl_merchant_special SET status=1, published_time=NOW() WHERE id=:id AND id_merchant=:id_merchant AND status=0');
		$command->execute(array('id'=>$id, 'id_merchant'=>Yii::app()->user->id));
		$connection->active = false;
		
		//notification for this published special
		//BUtils::PushNotificationToDevices($id);//don't use this way, instead to use the asyc-way
		if (!empty($id)) {
			$request_url = Yii::app()->createAbsoluteUrl($this->id . '/notifyOffer', array('id'=>$id));
			$ch = curl_init();
			curl_setopt($ch, CURLOPT_URL, $request_url);
			curl_setopt($ch, CURLOPT_TIMEOUT, 1);
			curl_exec($ch);
			curl_close($ch);
		}
	}
	
	/**
	 * Push notification for an offer.
	 * @param int $id offer ID
	 */
	public function actionNotifyOffer($id) {
		$demo = Yii::app()->getGlobalState('demo', false);
		if (YII_DEBUG) {
			$demo = true;
		}
		
		//apidev don't care about the night time
		BUtils::PushNotificationToDevices($id, $demo);
	}
	
	/**
	 * AJAX delete an offer.
	 */
	public function actionDelete($id) {
		//delete current special (only for status=0)
		$connection = Yii::app()->db;
		$command = $connection->createCommand('UPDATE tbl_merchant_special SET trash=1, trash_time=NOW() WHERE id=:id AND id_merchant=:id_merchant');
		$command->execute(array('id'=>$id, 'id_merchant'=>Yii::app()->user->id));
		$connection->active = false;
	}

	public function actionPreview($id) {
		$sql_offer = 'SELECT s.id, s.id_merchant, s.url_picture, s.content, m.url_offer_img, 
			s.price, s.value, s.discount, s.show_hours, s.start_hour, s.end_hour, s.week_days, s.type, s.max_number, s.redeem_type,
			UNIX_TIMESTAMP(s.published_time) AS uts_published_time,
			UNIX_TIMESTAMP(s.start_date) AS uts_start_date, UNIX_TIMESTAMP(s.end_date) AS uts_end_date,
			m.name, m.address, m.biz_area, m.postcode, m.city, m.phone, m.url_logo, m.currency_code, m.category_key, m.latitude, m.longitude
			FROM tbl_merchant_special s
			INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE s.id=:id AND m.id=:id_merchant ';
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_offer);
		$row = $command->queryRow(true, array(':id'=>$id, ':id_merchant'=>Yii::app()->user->id));
		$connection->active = false;
		
		//search for thumbs
		$row['thumbs'] = array();
		
		if (empty($row)) {
			throw new CHttpException(404, 'The requested page does not exist.');
		}
		
		$this->renderPartial('_preview', array('r' => $row));
	}
	
	/**
	 * Redeem a special with a yamii code.
	 * Notes: The merchant enters yamii code which is from a visited user.
	 * code=?
	 */
	public function actionRedeem() {
		$code = Yii::app()->request->getParam('code', null);
		if (empty($code)) {
			echo BUtils::T('special_redeem_null_msg');;
			Yii::app()->end();
		}
		
		$sql_redeem = 'SELECT r.id, r.code, r.id_user, r.id_special, r.redeemed, r.redeemed_time, r.insert_timestamp,
			UNIX_TIMESTAMP(r.redeemed_time) AS uts_redeemed
			FROM tbl_merchant_special_redeem r
			INNER JOIN tbl_merchant_special s ON r.id_special=s.id
			WHERE r.code=:code AND s.id_merchant=:id_merchant';
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_redeem);
		$row = $command->queryRow(true, array(
			'code' => $code,
			'id_merchant' => Yii::app()->user->id,
		));
		if (empty($row)) {
			$error = 1;
			$message = BUtils::T('special_redeem_invalid_msg');
		} else if ($row['redeemed'] == 1) {
			$error = 2;
			// 'long', 'medium' and 'short'
			$redeemed_time = Yii::app()->locale->dateFormatter->formatDateTime($row['uts_redeemed'], 'medium');
			$message = BUtils::T('special_redeem_existed_msg', array('{redeemed_time}'=>$redeemed_time));
		} else {
			$error = 0;
			$message = BUtils::T('special_redeem_valid_msg');
		}
		if ($error === 0) {
			//update status with yamii code
			$sql_redeem_update = 'UPDATE tbl_merchant_special_redeem SET redeemed=1, redeemed_time=NOW() WHERE id=:id';
			$command = $connection->createCommand($sql_redeem_update);
			$command->execute(array('id'=>$row['id']));
			$message = '<span style="color:green;">' . $message . '</span>';
		} else {
			//insert redeem log table
			$sql_redeem_failed = 'INSERT INTO tbl_merchant_special_redeem_log (error, code, message) VALUES (:error, :code, :message)';
			$command = $connection->createCommand($sql_redeem_failed);
			$command->execute(array('code'=>$code, 'message'=>$message, 'error'=>$error));
			$message = '<span style="color:red;">' . $message . '</span>';
		}
		$connection->active = false;
		
		echo $message;
	}
	
	/**
	 * List special daily reports.
	 * id - offer id
	 */
	public function actionReportDaily($id) {
		if (empty($id)) {
			throw new CHttpException(404, 'The parameter "id" is missing!');
		}
		
		$sql_report = "SELECT d.local_date, UNIX_TIMESTAMP(d.local_date) AS ts_local_date,
			    d.id_special, d.reach, d.clicks, d.notifications, d.spread, d.redeems,
				DATE(s.start_date) AS start_date, DATE(s.end_date) AS end_date,
				UNIX_TIMESTAMP(s.start_date) AS uts_start_date, UNIX_TIMESTAMP(s.end_date) AS uts_end_date
			FROM tbl_merchant_special_report_day d
			INNER JOIN tbl_merchant_special s ON s.id=d.id_special
			INNER JOIN tbl_merchant_account m ON m.id=s.id_merchant
			WHERE d.id_special=:id_special AND s.id_merchant=:id_merchant AND s.trash=0
			ORDER BY d.local_date ASC ";
		$params = array(
			':id_special' => $id,
			':id_merchant' => Yii::app()->user->id,
		);
		$connection = Yii::app()->db;
		$command = $connection->createCommand($sql_report);
		$rows = $command->queryAll(true, $params);
		$connection->active = false;
		if (empty($rows)) {
			Yii::app()->end();
		}
		
		if ($rows[0]['start_date'] == $rows[0]['end_date']) {
			$this->renderPartial('_chart_one', array(
				'rows' => $rows,
			));
		} else {
			$this->renderPartial('_chart_daily', array(
				'rows' => $rows,
			));
		}
	}

	/**
	 * TODO: Create special code when user click get button.
	 * This function will be moved to users page.
	 */
	public function actionCode($id) {
		if ($id < 1) throw new CHttpException(404, 'The requested page does not exist.');
		
		//check table tbl_merchant_special_redeem
		//redeemed_timestamp - INTERVAL 12 HOUR > NOW(): user cannot get new special until it has been redeemed for 12 hours.
		//OR redeemed_timestamp IS NULL: or user didn't use it (wasn't redeemed by merchant)
		//CRON JOB: every month, data transfer job will move all redeemed special for one month ago. (tbl_merchant_special_redeem_hist)
		$connection = Yii::app()->db;
		$params = array('id_special'=>$id, 'id_user'=>Yii::app()->user->id);
		$sql_redeem = 'SELECT id, code, insert_timestamp, redeemed, redeemed_time
			FROM tbl_merchant_special_redeem
			WHERE id_special=:id_special AND id_user=:id_user
			  AND ((redeemed_time > NOW() - INTERVAL 12 HOUR) OR redeemed_time IS NULL)
			ORDER BY redeemed_time DESC LIMIT 1';
		$command = $connection->createCommand($sql_redeem);
		$row = $command->queryRow(true, $params);
		if (empty($row)) {
			//insert
			$sql_redeem_new = 'INSERT INTO tbl_merchant_special_redeem (id_user, id_special) VALUES (:id_user, :id_special)';
			$command = $connection->createCommand($sql_redeem_new);
			$command->execute($params);
			
			$sql_redeem = 'SELECT id FROM tbl_merchant_special_redeem
				WHERE id_special=:id_special AND id_user=:id_user AND redeemed_time IS NULL
				ORDER BY insert_timestamp DESC LIMIT 1';
			$command = $connection->createCommand($sql_redeem);
			$row = $command->queryRow(true, $params);
			$redeem_id = $row['id'];
			
			$code = BUtils::encode($redeem_id);
			//update redeem code to table
			$sql_update = 'UPDATE tbl_merchant_special_redeem SET code=:code WHERE id=:id';
			$command = $connection->createCommand($sql_update);
			$command->execute(array('code'=>$code, 'id'=>$redeem_id));
		} else {
			$redeem_id = $row['id'];
		}
		$connection->active = false;
		
		$code = BUtils::encode($redeem_id);  // redemption code = encode(redeem_id)
		$url = $code;	                     // redeem link: merchant use this link to redeem special.
		
		//print out HTML for redemption code
		echo '<div class="redemption_code">' . BUtils::T('special_redemption_code_lbl') . ': <span>' . $code . '</span></div>';
		echo '<div class="redemption_qrcode">';
		$this->widget('application.extensions.qrcode.QRCodeGenerator',array(
			'data' => $url,
			'subfolderVar' => true,
			'filename' => $code.'.png',
			'matrixPointSize' => 3,
		));
		echo '</div>';
		echo '<div class="redemption_code_tips">' . BUtils::T('how_to_use_redemption_code_eg') . '</div>';
		echo '<div class="clear"></div>';
	}
	
	/**
	 * Returns the data model based on the primary key given in the GET variable.
	 * If the data model is not found, an HTTP exception will be raised.
	 * @param integer the ID of the model to be loaded
	 */
	protected function _loadModel($id) {
		$model = SpecialForm::model()->findByPk(
			$id,
			'id_merchant=:id_merchant AND trash=0',
			array('id_merchant'=>Yii::app()->user->id)
		);
		if ($model===null)
			throw new CHttpException(404, 'The requested page does not exist.');
		return $model;
	}
}